package com.zhtools.utils;

import java.util.ArrayList;
import java.util.List;

/**
 * @author zhanghao
 * 集合工具类
 */
public class CollectionUtils {
    /**
     * 集合笛卡尔积
     *
     * @param list
     * @param <T>
     * @return
     */
    public static <T> List<List<T>> descartes(List<List<T>> list) {
        if (list == null || list.size() == 0 || list.size() == 1) {
            return list;
        }
        List<List<T>> result = new ArrayList<>();//最终结果
        List<T> list1 = list.get(0);//获取第一组集合
        for (int i = 1; i < list.size(); i++) {//从第二组集合开始组合
            if (i == 1) {//第一次组合
                result = assemble1(list1, list.get(i));
            } else {
                result = assemble2(result, list.get(i));
            }
        }
        return result;
    }

    /**
     * 组合
     *
     * @param list1
     * @param list2
     * @param <T>
     * @return
     */
    private static <T> List<List<T>> assemble1(List<T> list1, List<T> list2) {
        List<List<T>> result = new ArrayList<>();
        for (int i = 0; i < list1.size(); i++) {
            for (int j = 0; j < list2.size(); j++) {
                List<T> assemble = new ArrayList<>();
                assemble.add(list1.get(i));
                assemble.add(list2.get(j));
                result.add(assemble);
            }
        }
        return result;
    }

    /**
     * 组合
     *
     * @param list1
     * @param list2
     * @param <T>
     * @return
     */
    private static <T> List<List<T>> assemble2(List<List<T>> list1, List<T> list2) {
        List<List<T>> result = new ArrayList<>();
        for (int i = 0; i < list1.size(); i++) {
            for (int j = 0; j < list2.size(); j++) {
                List<T> assemble = new ArrayList<>();
                assemble.addAll(list1.get(i));
                assemble.add(list2.get(j));
                result.add(assemble);
            }
        }
        return result;
    }
}
